#include <iostream>
#include <cstring>
using namespace std;

class Matrix
{
    friend Matrix operator*(Matrix &m0,Matrix &m);
public:
    int n_row;
    int n_col;
    int **data;

    Matrix()
	{
	    n_row=0;
	    n_col=0;
	    data=nullptr;
	}
    
    Matrix(int t,int s)
	{
	    n_row=t;
	    n_col=s;
	    data=new int*[n_row];
	    for(int i=0;i<n_row;i++)
	        data[i]=new int[n_col];
	}

    Matrix (const Matrix& M)
	{
		n_col = M.n_col;
		n_row = M.n_row;
		data = new int *[n_row];
		for(int i=0; i<n_row; i++)
		{
		    data[i]=new int[n_col];
		    memcpy(data[i],M.data[i],sizeof(int)*n_col);
		}
	}

    Matrix & operator=(const Matrix & m)
    	{
	  
	    for (int i = 0; i < n_row; i++)
		delete[] data[i];
	    delete[]data;
	    this->n_col = m.n_col;
	    this->n_row = m.n_row;
	    data = new int *[n_row];
	    for (int i = 0; i < n_row; i++)
	    {
		data[i] = new int[n_col];
		memcpy(data[i], m.data[i], sizeof(int)*n_col);
	    }
	    return *this;
    	}

    int * operator[](const int &i)
	{
	    return data[i];
	}

    void putMatrix()
	{
	    for(int i=0;i<n_row;i++)
		for(int j=0;j<n_col;j++)
		    std::cin>>data[i][j];
	}
    
    void print()
	{
	    for(int i=0;i<n_row;i++)
	    {
		for(int j=0;j<n_col;j++)
		    std::cout<<data[i][j]<<"\t";
		std::cout<<endl;
	    }
	}

    ~Matrix()
	{
	    for(int i=0;i<n_row;i++)
		delete[] data[i];
	    delete []data;
	    data=nullptr;
	}

    bool is_square(int t,int s)
	{
	    n_row=t;
	    n_col=s;
	    if(n_row==n_col)
		return true;
	    else
		return false;
	}
    
    
};


Matrix operator*(Matrix &m0,Matrix &m)
{
    if (m0.n_col != m.n_row)
    {
	std::cout<<"can not calculate!"<<endl;
	exit(0);
    }

	      
    Matrix result(m0.row,m.col);
    for (int i = 0; i < result.n_row; i++)
	for (int j = 0; j < result.n_col; j++)
	{
	    result[i][j] = 0;
	    for (int k = 0; k < m0.n_col; k++)
		result[i][j] += m0[i][k] * m[k][j];
	}
    return result;
}


class RowVector:public Matrix
{
    friend Matrix operator*(RowVector &m0,RowVector &m);
public:

   
    RowVector(int c)
	{
	    n_row=1;
	    n_col=c;
	    data=new int*[n_row];
	    for(int i=0;i<n_row;i++)
	        data[i]=new int[n_col];
	}

    RowVector (const Matrix& M)
    	{
    	    n_col = M.n_col;
    	    n_row = M.n_col;
    	    data = new int *[n_row];
    	    for(int i=0; i<n_row; i++)
    	    {
    		data[i]=new int[n_col];
    		memcpy(data[i],M.data[i],sizeof(int)*n_col);
    	    }
    	}
    

};



class ColVector:public Matrix
{
public:
    ColVector(int r)
	{
	    n_row=r;
	    n_col=1;
	    data=new int*[n_row];
	    for(int i=0;i<n_row;i++)
	        data[i]=new int[n_col];
	}

};

Matrix operator*(RowVector &m0,RowVector &m)
{
    if(m0.n_col!=m.n_col)
    {
	std::cout<<"can not calculate!"<<endl;
	exit(0);
    }

    Matrix result(1,1);
    for (int i = 0; i < m.n_row; i++)
	for (int j = 0; j < m.n_row; j++)
	{
	    result[i][j] = 0;
	    for (int k = 0; k < m.n_col; k++)
		result[i][j] += m0[0][k] * m[0][k];
	}
    return result;
}
